home *** CD-ROM | disk | FTP | other *** search
- /* file: BigEasyVideoGrabber.c
- *
- * Started 18 December 1991
- *
- * A set of routines for using the
- * somewhat baroque and, perhaps, spurious
- * video-digitizer and sequence-grabber
- * component interfaces.
- *
- * It implements the one straight-ahead
- * routine: GrabFrame.
- *
- */
-
-
-
- /*--------------------------
- Inclusions
- --------------------------*/
-
- #include <Memory.h>
- #include <OSUtils.h>
- #include "BigEasyVideoGrabber.h"
-
-
- /*--------------------------
- Routines
- --------------------------*/
-
-
- EasyVideoGrabber NewEasyVideoGrabber(Rect *outputSize)
- /*
- * Gets the default video digitizer,
- * and returns the output size of the video image.
- */
- {
- EasyVideoGrabber evg;
- ComponentResult thisError;
-
- evg = (void *)NewPtr(sizeof(EasyVideoGrabberRecord));
- if(!evg)
- goto fail;
-
- evg->sg = 0;
- evg->vc = 0;
-
- evg->sg = OpenDefaultComponent(SeqGrabComponentType, 0);
- if(!evg->sg)
- goto fail;
-
- thisError = SGInitialize(evg->sg);
- if(thisError)
- goto fail;
-
- thisError = SGNewChannel(evg->sg, VideoMediaType, &evg->vc);
- if(thisError)
- goto fail;
-
- if(outputSize)
- {
- thisError = SGGetSrcVideoBounds(evg->vc, outputSize);
- if(thisError)
- goto fail;
- }
-
- thisError = SGSetChannelUsage(evg->vc, seqGrabPreview);
- if(thisError)
- goto fail;
-
- goto goHome;
-
- fail:
- if(evg)
- {
- if(evg->sg)
- CloseComponent(evg->sg);
- DisposePtr((void *)evg);
- evg = 0;
- }
-
- goHome:
- return evg;
- }
-
-
- Boolean GrabEasyVideoGrabber(EasyVideoGrabber evg,Rect *r)
- /*
- * Grab a frame, and draw it in the current port, of size 'r'.
- * You can pass 'nil' for the EasyVideoGrabber, and one
- * will be allocated and disposed, while-u-wait.
- *
- * The boolean returned is 'true' iff a frame was actually captured and drawn.
- *
- * The 'while' loop is a real barnstorming technique. The "Sequence Grab"
- * component does not provide any way to know when a frame has actually
- * been grabbed. Therefore, the Sequence Grabber is simply idled for
- * a few ticks, on the _assumption_ that the video frame rate is high
- * enough that at least one frame is grabbed.
- *
- * While this may seem mildly inelegant, it, in fact, works.
- */
- {
- ComponentResult thisError;
- GWorldPtr gw;
- GDHandle gd;
- Boolean localGrabber;
- unsigned long t;
- Boolean result;
-
- result = false;
-
- localGrabber = (evg == 0);
- if(localGrabber)
- evg = NewEasyVideoGrabber(nil);
-
- if(!evg)
- goto goHome;
-
- GetGWorld(&gw,&gd);
-
- thisError = SGSetGWorld(evg->sg,gw,gd);
- if(thisError)
- goto goHome;
-
- thisError = SGSetChannelBounds(evg->vc,r);
- if(thisError)
- goto goHome;
-
- thisError = SGStartPreview(evg->sg);
- if(thisError)
- goto goHome;
-
- t = TickCount() + 8;
- do
- {
- thisError = SGIdle(evg->sg);
- if(thisError)
- goto goHome;
- } while (TickCount() < t);
-
- thisError = SGStop(evg->sg);
-
- if(localGrabber)
- DisposeEasyVideoGrabber(evg);
-
- result = true;
-
- goHome:;
- return result;
- }
-
- void DisposeEasyVideoGrabber(EasyVideoGrabber evg)
- {
- CloseComponent(evg->sg);
- DisposePtr( (void *)evg);
- }
-
-